﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading;
using System.Windows.Forms;

namespace SnmpForm.ApSearch
{
    public partial class FrmApSearch : FrmSub
    {
        public FrmApSearch(MainForm objMain):base(objMain)
        {
            InitializeComponent();
        }
        private Thread threadSearch = null;
        private SearchTask task = null;
        Dictionary<string, DbWrapper.DbDataTypes.Ap> mapApFinded =
            new Dictionary<string, DbWrapper.DbDataTypes.Ap>();
        private void FrmApSearch_Load(object sender, EventArgs e)
        {
            //实例化委托 
            displayLog = new DisplayLog(DisplayLogMethod);
            updateProgress = new UpdateProgress(UpdateProgressMethod);
            newApFinded = new NewApFinded(NewApFindMethod);
            taskIsStoped = new TaskIsStoped(TaskIsStopedMethod);

            //初始化AP操作按钮
            Button button = null;
            //bool bPrivelege = false;

            button = new Button();
            button.Text = "全选";
            button.Click += new System.EventHandler(this.ToolButtonApSelectAll_Click);
            flowLayoutPanelButtons.Controls.Add(button);

            button = new Button();
            button.Text = "全部取消";
            button.Click += new System.EventHandler(this.ToolButtonApCancleAllSelected_Click);
            flowLayoutPanelButtons.Controls.Add(button);

            button = new Button();
            button.Text = "加入托管列表";
            button.Click += new System.EventHandler(this.ToolButtonAddToTrust_Click);
            flowLayoutPanelButtons.Controls.Add(button);

            //listView
            listViewAp.View = View.Details;
            listViewAp.FullRowSelect = true;
            listViewAp.Columns.Add("id");
            listViewAp.Columns.Add("标识码", 200);
            listViewAp.Columns.Add("托管ip", 200);
            listViewAp.Columns.Add("是否已托管", 100);

            //自定义画图事件
            listBoxLog.DrawMode = DrawMode.OwnerDrawFixed;

            progressBarSearch.Minimum = 0;
            progressBarSearch.Maximum = 100;
        }

        private void UpdateView()
        {
            listViewAp.Items.Clear();

            int nIndex = 0;
            foreach (DbWrapper.DbDataTypes.Ap apinfo in mapApFinded.Values)
            {
                ListViewItem lvi = new ListViewItem();
                lvi.Text = (nIndex + 1).ToString();
                lvi.SubItems.Add(apinfo.mark);
                lvi.SubItems.Add(apinfo.manage_ip);
                //判定该设备是否已托管
                string strTrust = "";
                BusinessWrapper.Ap ap =
                    BusinessWrapper.User.Instance.GetAp(apinfo.ip);
                if (ap != null)
                {
                    strTrust = "已托管";
                }
                lvi.SubItems.Add(strTrust);

                listViewAp.Items.Add(lvi);

                nIndex++;
            }
        }

        //创建一个委托，是为访问listViewLog控件服务的。         
        public delegate void DisplayLog(string log);
        //定义一个委托变量         
        public DisplayLog displayLog;

        public void DisplayLogMethod(string log)
        {
            AddLog(log);
        }

        public class LogItem:Object
        {
            public LogItem(string msg, bool notice)
            {
                Msg = msg;
                bNotice = notice;
            }
            public override string ToString()
            {
                return Msg;
            }
            public string Msg;
            public bool bNotice;
        }
        public void AddLog(string log, bool bNotice = false)
        {
            string strText = DateTime.Now.ToString() + log;
            LogItem item = new LogItem(strText, bNotice);
            listBoxLog.Items.Add(item);
            //移到最后一行
            listBoxLog.TopIndex = listBoxLog.Items.Count - 1;
        }

        public delegate void UpdateProgress(int nProcess);
        public UpdateProgress updateProgress;
        private void UpdateProgressMethod(int nProgress)
        {
            if (threadSearch == null ||
                threadSearch.ThreadState == ThreadState.Stopped)
            {
                progressBarSearch.Value = 0;
                buttonStart.Enabled = true;
            }
            else
            {
                progressBarSearch.Value = nProgress;
            }
        }

        public delegate void NewApFinded(DbWrapper.DbDataTypes.Ap apinfo);
        public NewApFinded newApFinded;

        private void NewApFindMethod(DbWrapper.DbDataTypes.Ap apinfo)
        {
            if (!mapApFinded.ContainsKey(apinfo.mark))
            {
                //判定该设备是否已托管
                BusinessWrapper.Ap ap =
                    BusinessWrapper.User.Instance.GetAp(apinfo.mark);
                string strLog = "";
                if (ap == null)
                {
                    mapApFinded.Add(apinfo.mark, apinfo);

                    ListViewItem lvi = new ListViewItem();
                    lvi.Text = mapApFinded.Count.ToString();
                    lvi.SubItems.Add(apinfo.mark);
                    lvi.SubItems.Add(apinfo.manage_ip);
                    listViewAp.Items.Add(lvi);

                    strLog = "发现未托管设备";
                }
                else
                {
                    strLog = "发现已托管设备";
                }

                strLog = strLog + ":" + apinfo.mark;

                AddLog(strLog, ap==null);
            }
        }

        public delegate void TaskIsStoped();
        public TaskIsStoped taskIsStoped;
        private void TaskIsStopedMethod()
        {
            UpdateProgressMethod(0);
            buttonStart.Enabled = true;
        }

        private void buttonStart_Click(object sender, EventArgs e)
        {
            if (threadSearch == null||
                threadSearch.ThreadState == ThreadState.Stopped)
            {
                List<DbWrapper.DbDataTypes.SearchTarget> listTarget =
                    BusinessWrapper.User.Instance.GetSearchTargetList();
                if (listTarget.Count > 0)
                {
                    task = new SearchTask(this, listTarget);
                    threadSearch = new Thread(task.TaskFunction);
                    threadSearch.Start();
                    DisplayLogMethod("开始搜索");
                    buttonStart.Enabled = false;
                }
                else
                {
                    MessageBox.Show("没有可搜索的网络");
                }
            }
            else
            {
                MessageBox.Show("已有任务在运行");
            }
        }

        private void StopSearchTask()
        {
            if (threadSearch != null)
            {
                if (threadSearch.ThreadState != ThreadState.Stopped)
                {
                    threadSearch.Abort();
                    DisplayLogMethod("用户停止搜索");
                    UpdateProgressMethod(0);
                    buttonStart.Enabled = true;
                }
            }
        }

        private void buttonStop_Click(object sender, EventArgs e)
        {
            StopSearchTask();
        }

        private DbWrapper.DbDataTypes.Ap GetSelectedAp()
        {
            DbWrapper.DbDataTypes.Ap ap = null; ;
            string strMark = null;

            if (listViewAp.SelectedItems.Count > 0)
            {
                ListViewItem item = listViewAp.SelectedItems[0];
                strMark = item.SubItems[1].Text;
                ap = mapApFinded[strMark];
            }
            return ap;
        }

        private void ToolButtonApCancleAllSelected_Click(object sender, EventArgs e)
        {
            foreach (ListViewItem item in listViewAp.Items)
            {
                item.Checked = false;
            }
        }

        private void ToolButtonApSelectAll_Click(object sender, EventArgs e)
        {
            foreach (ListViewItem item in listViewAp.Items)
            {
                item.Checked = true;
            }
        }

        /// <summary>
        /// 将列表中勾选的AP加入托管列表中
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void ToolButtonAddToTrust_Click(object sender, EventArgs e)
        {
            int nAdd = 0;
            foreach (ListViewItem item in listViewAp.Items)
            {
                if (item.Checked)
                {
                    DbWrapper.DbDataTypes.Ap ap = null; ;
                    string strMark = null;
                    strMark = item.SubItems[1].Text;
                    ap = mapApFinded[strMark];
                    AddToTrust(ap);
                    nAdd++;
                }
            }

            if (nAdd > 0)
            {
                MessageBox.Show("添加完成");
                //更新
                UpdateView();
                //重新加载故障检测任务
                RestartDetectFaultTask();
            }
        }

        private bool AddToTrust(DbWrapper.DbDataTypes.Ap apinfo)
        {
            bool bAddToDb = true;
            //判定该AP是否已经托管
            BusinessWrapper.Ap ap =
                BusinessWrapper.User.Instance.GetAp(apinfo.mark);
            if (ap != null)
            {
                DialogResult result =
                    MessageBox.Show("该AP已经托管，是否重复添加",
                        "告警",
                        MessageBoxButtons.YesNo);
                if (result == DialogResult.Yes)
                {
                    bAddToDb = true;
                }
                else
                {
                    bAddToDb = false;
                }
            }
            else
            {
                bAddToDb = true;
            }
            if (bAddToDb)
            {
                //添加默认账户和密码
                apinfo.snmp_user = Properties.Settings.Default.SnmpDefaultUser;
                apinfo.snmp_password = Properties.Settings.Default.SnmpDefaultPassword;
                //添加到数据库中
                bool bAddtoDb =
                    BusinessWrapper.User.Instance.CreateAp(apinfo);
                if (bAddtoDb)
                {
                    //删除列表中的该项
                    mapApFinded.Remove(apinfo.mark);
                }
                
            }
            return bAddToDb;
        }

        private void ToolStripMenuItemAddToTrust_Click(object sender, EventArgs e)
        {
            DbWrapper.DbDataTypes.Ap apinfo = GetSelectedAp();
            if(apinfo!=null){
                if (AddToTrust(apinfo))
                {
                    MessageBox.Show("添加成功");
                    //更新
                    UpdateView();
                    //重新加载故障检测任务
                    RestartDetectFaultTask();
                }
                else
                {
                    MessageBox.Show("添加失败");
                }
            }
        }

        private void ToolStripMenuItemDel_Click(object sender, EventArgs e)
        {
            DbWrapper.DbDataTypes.Ap apinfo = GetSelectedAp();
            if (apinfo != null)
            {
                //删除列表中的该项
                mapApFinded.Remove(apinfo.mark);
                UpdateView();
            }
        }

        private void contextMenuStripAp_Opening(object sender, CancelEventArgs e)
        {
            DbWrapper.DbDataTypes.Ap apinfo = GetSelectedAp();
            if (apinfo == null)
            {
                e.Cancel = true;
            }
        }

        /// <summary>
        /// 自定义ListBox控件的刷新事件，notice事件需要红色字体标注
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void listBoxLog_DrawItem(object sender, DrawItemEventArgs e)
        {
            // Draw the background of the ListBox control for each item.
            e.DrawBackground();
            // Define the default color of the brush as black.
            Brush myBrush = Brushes.Black;

            LogItem item = (LogItem)listBoxLog.Items[e.Index];
            if (item.bNotice)
            {
                myBrush = Brushes.OrangeRed;
            }

            // Draw the current item text based on the current Font  
            // and the custom brush settings.
            e.Graphics.DrawString(item.Msg,
                e.Font, myBrush, e.Bounds, StringFormat.GenericDefault);
            // If the ListBox has focus, draw a focus rectangle around the selected item.
            e.DrawFocusRectangle();
        }

        private void FrmApSearch_FormClosing(object sender, FormClosingEventArgs e)
        {
            StopSearchTask();
        }
    
    }
}
